﻿using System;
using System.Diagnostics;
using System.Globalization;
using System.Runtime.InteropServices;
using System.ComponentModel.Design;
using Microsoft.Win32;
using Microsoft.VisualStudio;
using Microsoft.VisualStudio.Shell.Interop;
using Microsoft.VisualStudio.OLE.Interop;
using Microsoft.VisualStudio.Shell;
using Microsoft.SharepointSnifferPackage;
using EnvDTE80;
using EnvDTE;
using System.Xml;
using System.Text;
using System.IO;
using System.ServiceProcess;
using System.Threading;


namespace ServerExplorer.SharePointConnections.SharepointSiteInfo
{
    /// <summary>
    /// This is the class that implements the package exposed by this assembly.
    ///
    /// The minimum requirement for a class to be considered a valid package for Visual Studio
    /// is to implement the IVsPackage interface and register itself with the shell.
    /// This package uses the helper classes defined inside the Managed Package Framework (MPF)
    /// to do it: it derives from the Package class that provides the implementation of the 
    /// IVsPackage interface and uses the registration attributes defined in the framework to 
    /// register itself and its components with the shell.
    /// </summary>
    // This attribute tells the PkgDef creation utility (CreatePkgDef.exe) that this class is
    // a package.
    [PackageRegistration(UseManagedResourcesOnly = true)]
    // This attribute is used to register the informations needed to show the this package
    // in the Help/About dialog of Visual Studio.
    [InstalledProductRegistration("#110", "#112", "1.0", IconResourceID = 400)]
    // This attribute is needed to let the shell know that this package exposes some menus.
    //[ProvideMenuResource("Menus.ctmenu", 1)]
    // This attribute registers a tool window exposed by this package.
    [ProvideToolWindow(typeof(ToolWindowSharepointSniffer))]
    [Guid(GuidList.guidSharepointSnifferPackagePkgString)]
    public sealed class SharepointSnifferPackagePackage : Package
    {
        /// <summary>
        /// Default constructor of the package.
        /// Inside this method you can place any initialization code that does not require 
        /// any Visual Studio service because at this point the package object is created but 
        /// not sited yet inside Visual Studio environment. The place to do all the other 
        /// initialization is the Initialize method.
        /// </summary>
        public SharepointSnifferPackagePackage()
        {
            Trace.WriteLine(string.Format(CultureInfo.CurrentCulture, "Entering constructor for: {0}", this.ToString()));
        }

        //Funcao para usada para chamada externa para exibir e mostrar janela.
        public void showWnd()
        {
            ShowToolWindow(this, null);
        }

        /// <summary>
        /// This function is called when the user clicks the menu item that shows the 
        /// tool window. See the Initialize method to see how the menu item is associated to 
        /// this function using the OleMenuCommandService service and the MenuCommand class.
        /// </summary>
        private void ShowToolWindow(object sender, EventArgs e)
        {
            ServiceController[] scServices;
            scServices = ServiceController.GetServices();
           
            // Get the instance number 0 of this tool window. This window is single instance so this instance
            // is actually the only one.
            // The last flag is set to true so that if the tool window does not exists it will be created.
            ToolWindowPane window = this.FindToolWindow(typeof(ToolWindowSharepointSniffer), 0, true);
            if ((null == window) || (null == window.Frame))
            {
                throw new NotSupportedException(Resources.CanNotCreateWindow);
            }

            IVsWindowFrame windowFrame = (IVsWindowFrame)window.Frame;
            int err = Microsoft.VisualStudio.ErrorHandler.ThrowOnFailure(windowFrame.Show());
            if (err == Microsoft.VisualStudio.VSConstants.S_OK)
            {
                Access.frameRet = windowFrame;
            }
        }

        /////////////////////////////////////////////////////////////////////////////
        // Overriden Package Implementation
        #region Package Members

        /// <summary>
        /// Initialization of the package; this method is called right after the package is sited, so this is the place
        /// where you can put all the initilaization code that rely on services provided by VisualStudio.
        /// </summary>
        protected override void Initialize()
        {
            Trace.WriteLine(string.Format(CultureInfo.CurrentCulture, "Entering Initialize() of: {0}", this.ToString()));
            base.Initialize();
            Access.fsh = showWnd;
            Access.XmlView = CreateNewXmlFile;
        }

        /// <summary>
        /// Adds new file to the current Solution/Project and inserts the contents
        /// </summary>
        /// <param name="fileType">File type, eg. General\XML File</param>
        /// <param name="title">File title</param>
        /// <param name="fileContents">File contents</param>
        internal static void CreateNewFile(string fileType, string title, string fileContents)
        {
            DTE2 dte = Package.GetGlobalService(typeof(SDTE)) as DTE2;
            Window w = dte.ItemOperations.NewFile(fileType, title, EnvDTE.Constants.vsViewKindTextView);
            Document file = w.Document;
            if (!String.IsNullOrEmpty(fileContents))
            {
                TextSelection selection = (TextSelection)file.Selection;
                selection.SelectAll();
                selection.Text = "";
                selection.Insert(FormatXMLString(fileContents));
                selection.StartOfDocument();
            }
        }

        public static string FormatXMLString(string sUnformattedXML)
        {
            XmlDocument xd = new XmlDocument();
            xd.LoadXml(sUnformattedXML);
            StringBuilder sb = new StringBuilder();
            StringWriter sw = new StringWriter(sb);
            XmlTextWriter xtw = null;
            try
            {
                xtw = new XmlTextWriter(sw);
                xtw.Formatting = Formatting.Indented;
                xd.WriteTo(xtw);
            }
            finally
            {
                if (xtw != null)
                    xtw.Close();
            }
            return sb.ToString();
        }


        /// <summary>
        /// Creates new text file with the given title and contents
        /// </summary>
        /// <param name="title">File title</param>
        /// <param name="fileContents">File contents</param>
        public static void CreateNewXmlFile(string title, string fileContents)
        {
            CreateNewFile(@"General\XML File", title, fileContents);
        }

        #endregion

    }
}
